import json
import threading
from typing import Dict, List, Optional
from datetime import datetime

class TaskManager:
    def __init__(self, config):
        self.config = config
        self.download_queue: List[int] = []  # 存储待下载任务
        self.active_downloads: Dict[int, threading.Thread] = {}  # 存储正在下载的任务
        self.download_tasks: Dict[int, Dict] = {}  # 存储所有任务信息
        self.next_task_id = 1  # 任务ID计数器
        self.queue_lock = threading.Lock()  # 队列操作锁
        
        # 加载任务
        self.load_tasks()
    
    def load_tasks(self):
        """加载保存的任务"""
        try:
            if os.path.exists(self.config.tasks_file):
                with open(self.config.tasks_file, "r", encoding="utf-8") as f:
                    tasks_data = json.loads(f.read())
                    self.download_tasks = tasks_data.get("tasks", {})
                    self.next_task_id = tasks_data.get("next_task_id", 1)
                    
                    # 恢复未完成的任务
                    for task_id, task_info in self.download_tasks.items():
                        if task_info["status"] in ["queued", "downloading", "paused"]:
                            task_info["status"] = "queued"
                            self.download_queue.append(task_id)
        except Exception as e:
            print(f"加载任务失败: {str(e)}")
            self.download_tasks = {}
            self.next_task_id = 1
    
    def save_tasks(self):
        """保存任务状态"""
        try:
            tasks_data = {
                "tasks": self.download_tasks,
                "next_task_id": self.next_task_id
            }
            with open(self.config.tasks_file, "w", encoding="utf-8") as f:
                json.dump(tasks_data, f, ensure_ascii=False, indent=2)
        except Exception as e:
            print(f"保存任务失败: {str(e)}")
    
    def create_task(self, url: str, format_id: str, title: str, thumbnail: str, 
                   format_note: str, resolution: str, ext: str) -> int:
        """创建新任务"""
        with self.queue_lock:
            task_id = self.next_task_id
            self.next_task_id += 1
            
            task_info = {
                "id": task_id,
                "url": url,
                "format_id": format_id,
                "title": title,
                "thumbnail": thumbnail,
                "status": "queued",
                "progress": 0,
                "format_note": format_note,
                "resolution": resolution,
                "ext": ext,
                "created_at": datetime.now().isoformat(),
                "updated_at": datetime.now().isoformat()
            }
            
            self.download_tasks[task_id] = task_info
            self.download_queue.append(task_id)
            self.save_tasks()
            
            return task_id
    
    def update_task_progress(self, task_id: int, progress: float):
        """更新任务进度"""
        with self.queue_lock:
            if task_id in self.download_tasks:
                task_info = self.download_tasks[task_id]
                task_info["progress"] = progress
                task_info["updated_at"] = datetime.now().isoformat()
                self.save_tasks()
    
    def update_task_status(self, task_id: int, status: str, message: Optional[str] = None):
        """更新任务状态"""
        with self.queue_lock:
            if task_id in self.download_tasks:
                task_info = self.download_tasks[task_id]
                task_info["status"] = status
                if message:
                    task_info["message"] = message
                task_info["updated_at"] = datetime.now().isoformat()
                self.save_tasks()
    
    def cancel_task(self, task_id: int):
        """取消任务"""
        with self.queue_lock:
            # 检查任务是否在队列中
            if task_id in self.download_queue:
                self.download_queue.remove(task_id)
                self.update_task_status(task_id, "cancelled")
                return
            
            # 检查任务是否正在下载
            if task_id in self.active_downloads:
                self.update_task_status(task_id, "cancelled")
    
    def pause_task(self, task_id: int):
        """暂停任务"""
        with self.queue_lock:
            if task_id in self.download_queue:
                self.download_queue.remove(task_id)
                self.update_task_status(task_id, "paused")
            elif task_id in self.active_downloads:
                self.update_task_status(task_id, "paused")
    
    def resume_task(self, task_id: int):
        """恢复任务"""
        with self.queue_lock:
            if task_id in self.download_tasks:
                task_info = self.download_tasks[task_id]
                if task_info["status"] == "paused":
                    if task_id not in self.download_queue:
                        self.download_queue.append(task_id)
                    self.update_task_status(task_id, "queued")
    
    def get_task(self, task_id: int) -> Optional[Dict]:
        """获取任务信息"""
        return self.download_tasks.get(task_id)
    
    def get_all_tasks(self) -> List[Dict]:
        """获取所有任务"""
        return list(self.download_tasks.values())
    
    def get_active_tasks(self) -> List[Dict]:
        """获取活动任务"""
        return [task for task in self.download_tasks.values() 
                if task["status"] in ["queued", "downloading", "paused"]]
    
    def get_completed_tasks(self) -> List[Dict]:
        """获取已完成任务"""
        return [task for task in self.download_tasks.values() 
                if task["status"] == "completed"]
    
    def get_failed_tasks(self) -> List[Dict]:
        """获取失败任务"""
        return [task for task in self.download_tasks.values() 
                if task["status"] == "failed"] 